﻿using AdminBase.Common.Attributes;
using AdminBase.Common.Helpers;
using AdminBase.Interface;
using AdminBase.Model;
using AdminBase.Model.Common;
using AdminBase.Model.Entitys;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.StaticFiles;

namespace AdminBase.webapi.Controllers
{
    /// <summary>
    /// 文件控制器
    /// </summary>
    [ApiController]
    [Authorize]
    [Route("[controller]")]
    [ApiExplorerSettings(IgnoreApi = false, GroupName = nameof(ApiVersions.V1))]
    [TypeFilter(typeof(AsyncExceptionFilterAttribute))]
    public class FilesController : ControllerBase
    {
        // 文件业务接口
        private readonly IFilesService _service;
        // 静态文件夹接口
        private readonly IWebHostEnvironment _environment;

        /// <summary>
        /// 构造注入
        /// </summary>
        /// <param name="environment"></param>
        /// <param name="file"></param>
        public FilesController(IWebHostEnvironment environment, IFilesService file)
        {
            _environment = environment;
            _service = file;
        }

        /// <summary>
        /// 上传
        /// </summary>
        /// <param name="file"></param>
        /// <returns></returns>
        /// <exception cref="Exception"></exception>
        [HttpPost]
        public ApiResult Upload(IFormFile file)
        {
            if (file == null)
            {
                throw new Exception("请选择文件上传!");
            }
            var fileName = file.FileName;
            if (!FilesHelper.IsMatchFormat(fileName))
            {
                throw new Exception("请上传正确格式的文件!");
            }
            // 上限25M
            if (file.Length > 25 * 1024 * 1024)
            {
                throw new Exception("文件大小不能超过25M");
            }
            if (file.Length > 0)
            {
                string userName = HttpContext.User.Claims.FirstOrDefault(c => c.Type == "UserName")?.Value;
                // 检查或创建文件夹
                string userPath = Path.Combine(userName, DateTime.Now.ToString("yyyy-MM-dd"));
                if (FilesHelper.IsMatchFormat("image"))
                {
                    userPath = Path.Combine("images", userPath);
                }
                string fullPath = Path.Combine(_environment.WebRootPath, userPath);
                FilesHelper.CreateDir(fullPath);

                Files entity = new Files();
                entity.FileID = Guid.NewGuid().ToString().Replace("-", "").ToLower();
                entity.FileName = file.FileName;
                string suffix = Path.GetExtension(file.FileName);
                string newFileName = entity.FileID + suffix;
                entity.FilePath = Path.Combine(userPath, newFileName);

                fullPath = Path.Combine(_environment.WebRootPath, entity.FilePath);
                // 保存文件
                using (var stream = System.IO.File.Create(fullPath))
                {
                    file.CopyToAsync(stream);
                }

                entity.CreateUserName = HttpContext.User.Claims.FirstOrDefault(c => c.Type == "FullName")?.Value; // 获取当前登录人信息 
                entity.CreateDateTime = DateTime.Now;
                // 新增文件表数据
                _service.Add(entity);
                return ResultHelper.Success(entity);
            }
            return ResultHelper.Success("上传失败：文件为空");
        }

        /// <summary>
        /// 下载
        /// </summary>
        /// <param name="fileID"></param>
        /// <returns></returns>
        [HttpGet]
        public async Task<FileResult> Download(string fileID)
        {
            var file = _service.Get(fileID);
            if (file == null)
            {
                throw new Exception("文件不存在!");
            }

            string filePath = Path.Combine(_environment.WebRootPath, file.FilePath);
            var stream = System.IO.File.OpenRead(filePath);
            string fileExt = Path.GetExtension(filePath);
            // 获取文件的ContentType
            var provider = new FileExtensionContentTypeProvider();
            var memi = provider.Mappings[fileExt];

            return await Task.FromResult(File(stream, memi, Path.GetFileName(file.FileName)));
        }

        /// <summary>
        /// 删除
        /// </summary>
        /// <param name="fileID"></param>
        /// <returns></returns>
        [HttpDelete]
        public async Task<ApiResult> Delete(string fileID)
        {
            if (string.IsNullOrWhiteSpace(fileID))
            {
                return ResultHelper.Success("请选择文件删除!");
            }
            var file = _service.Get(fileID);
            if (file != null)
            {
                string fullPath = Path.Combine(_environment.WebRootPath, file.FilePath);
                if (System.IO.File.Exists(fullPath))
                {
                    System.IO.File.Delete(fullPath);
                }
                _service.Delete(fileID);
            }
            return ResultHelper.Success("成功");
        }
    }
}